package com.atguigu.tingshu.order.service.impl;

import com.alibaba.fastjson.JSON;
import com.atguigu.tingshu.account.client.UserAccountFeignClient;
import com.atguigu.tingshu.album.client.AlbumInfoFeignClient;
import com.atguigu.tingshu.album.client.TrackInfoFeignClient;
import com.atguigu.tingshu.common.constant.SystemConstant;
import com.atguigu.tingshu.common.execption.GuiguException;
import com.atguigu.tingshu.common.rabbit.constant.MqConst;
import com.atguigu.tingshu.common.rabbit.service.RabbitService;
import com.atguigu.tingshu.common.result.Result;
import com.atguigu.tingshu.common.result.ResultCodeEnum;
import com.atguigu.tingshu.model.album.AlbumInfo;
import com.atguigu.tingshu.model.album.TrackInfo;
import com.atguigu.tingshu.model.order.OrderDerate;
import com.atguigu.tingshu.model.order.OrderDetail;
import com.atguigu.tingshu.model.order.OrderInfo;
import com.atguigu.tingshu.model.payment.PaymentInfo;
import com.atguigu.tingshu.model.user.VipServiceConfig;
import com.atguigu.tingshu.order.helper.SignHelper;
import com.atguigu.tingshu.order.mapper.OrderDerateMapper;
import com.atguigu.tingshu.order.mapper.OrderDetailMapper;
import com.atguigu.tingshu.order.mapper.OrderInfoMapper;
import com.atguigu.tingshu.order.service.OrderInfoService;
import com.atguigu.tingshu.user.client.UserInfoFeignClient;
import com.atguigu.tingshu.user.client.VipServiceConfigFeignClient;
import com.atguigu.tingshu.vo.account.AccountDeductVo;
import com.atguigu.tingshu.vo.order.OrderDerateVo;
import com.atguigu.tingshu.vo.order.OrderDetailVo;
import com.atguigu.tingshu.vo.order.OrderInfoVo;
import com.atguigu.tingshu.vo.order.TradeVo;
import com.atguigu.tingshu.vo.user.UserInfoVo;
import com.atguigu.tingshu.vo.user.UserPaidRecordVo;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import io.seata.spring.annotation.GlobalTransactional;
import lombok.extern.slf4j.Slf4j;
import org.apache.http.util.Asserts;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.core.script.DefaultRedisScript;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;

import java.math.BigDecimal;
import java.util.*;
import java.util.concurrent.TimeUnit;
import java.util.stream.Collectors;

@Slf4j
@Service
@SuppressWarnings({"all"})
public class OrderInfoServiceImpl extends ServiceImpl<OrderInfoMapper, OrderInfo> implements OrderInfoService {

    @Autowired
    private OrderInfoMapper orderInfoMapper;
    @Autowired
    private UserInfoFeignClient userInfoFeignClient;
    @Autowired
    private AlbumInfoFeignClient albumInfoFeignClient;
    @Autowired
    private RedisTemplate redisTemplate;
    @Autowired
    private VipServiceConfigFeignClient vipServiceConfigFeignClient;
    @Autowired
    private TrackInfoFeignClient trackInfoFeignClient;
    @Autowired
    private UserAccountFeignClient userAccountFeignClient;
    @Autowired
    private OrderDerateMapper orderDerateMapper;
    @Autowired
    private OrderDetailMapper orderDetailMapper;
    @Autowired
    private RabbitService rabbitService;


    @Override
    public OrderInfoVo trade(Long userId, TradeVo tradeVo) {
        //  创建返回对象
        OrderInfoVo orderInfoVo = new OrderInfoVo();
        //创建返回对象源属性
        BigDecimal originalAmount = new BigDecimal("0.00");//订单原始金额
        BigDecimal derateAmount = new BigDecimal("0.00"); //减免总金额
        BigDecimal orderAmount = new BigDecimal("0.00"); //订单总金额
        List<OrderDetailVo> orderDetailVoList = new ArrayList<>();//订单明细列表
        List<OrderDerateVo> orderDerateVoList = new ArrayList<>();//订单减免明细列表

        //情况1：购买专辑  通过itemType 进行判断购买情况
        if (SystemConstant.ORDER_ITEM_TYPE_ALBUM.equals(tradeVo.getItemType())) {
            //  获取到专辑Id
            Long albumnId = tradeVo.getItemId();
            //  需要远程调用查看是否购买过专辑！
            Result<Boolean> flag = userInfoFeignClient.isPaidAlbum(albumnId);
            //  判断返回值是否为空
            Asserts.notNull(flag, "用户购买专辑信息不存在");
            //取返回值 Result<Boolean> 的值
            Boolean flagData = flag.getData();
            //判断是否为空值
            Asserts.notNull(flagData, "用户购买专辑信息不存在");
            //判断是否购买过专辑
            if (flagData) {
                //  购买过专辑 直接返回 重复购买，请确认后会下单
                throw new GuiguException(ResultCodeEnum.REPEAT_BUY_ERROR);
            }
            //   根据专辑Id 远程调用专辑服务 获取到专辑对象；
            Result<AlbumInfo> albumInfo = albumInfoFeignClient.getAlbumInfo(albumnId);
            //  判断返回值是否为空
            Asserts.notNull(albumInfo, "专辑不存在");
            //取返回值 Result<AlbumInfo> 的值
            AlbumInfo albumInfoData = albumInfo.getData();
            //判断是否为空值
            Asserts.notNull(albumInfoData, "专辑不存在");

            originalAmount = albumInfoData.getPrice();//订单原始金额
            //远程调用用户模块，判断用户是否为vip
            Result<UserInfoVo> userInfoVo = userInfoFeignClient.getUserInfoVo(userId);
            Asserts.notNull(userInfoVo, "用户列表不存在");
            UserInfoVo userInfoVoData = userInfoVo.getData();
            Asserts.notNull(userInfoVoData, "用户不存在");
            //是vip 且vip过期时间在当前时间之后
            if (1 == userInfoVoData.getIsVip() && userInfoVoData.getVipExpireTime().after(new Date())) {
                //判断专辑是否有vip折扣
                if (albumInfoData.getVipDiscount().compareTo(new BigDecimal("-1")) == 1) {
                    //说明有折扣 赋值折扣价格 减免总金额 1000 2折； 折扣:800; 实际：200; 0.1--9.9;  1000*(10-2)/10=800;
                    derateAmount = originalAmount.multiply(new BigDecimal("10").subtract(albumInfoData.getVipDiscount())).divide(new BigDecimal("10"), 2, BigDecimal.ROUND_HALF_UP);
                }
            } else { //不是vip
                //判断专辑是否有普通折扣
                if (albumInfoData.getDiscount().compareTo(new BigDecimal("-1")) == 1) {
                    //说明有折扣 赋值折扣价格 减免总金额 1000 2折； 折扣:800; 实际：200; 0.1--9.9;  1000*(10-2)/10=800;
                    derateAmount = originalAmount.multiply(new BigDecimal("10").subtract(albumInfoData.getDiscount())).divide(new BigDecimal("10"), 2, BigDecimal.ROUND_HALF_UP);
                }

            }

            orderAmount = originalAmount.subtract(derateAmount);//订单总金额

            //订单 明细列表泛型
            OrderDetailVo orderDetailVo = new OrderDetailVo();
            orderDetailVo.setItemId(albumnId);//付费项目id
            orderDetailVo.setItemName(albumInfoData.getAlbumTitle());//付费项目名称
            orderDetailVo.setItemUrl(albumInfoData.getCoverUrl());//付费项目图片url
            orderDetailVo.setItemPrice(orderAmount);//付费项目价格
            //添加至订单 明细集合
            orderDetailVoList.add(orderDetailVo);

            //赋值 减免 明细，判断是否有减免
            if (derateAmount.compareTo(new BigDecimal("0")) == 1) {
                //订单减免明细列表泛型
                OrderDerateVo orderDerateVo = new OrderDerateVo();
                orderDerateVo.setDerateType(SystemConstant.ORDER_DERATE_ALBUM_DISCOUNT); //1405：订单减免类型 1405-专辑折扣 1406-VIP服务折
                orderDerateVo.setDerateAmount(derateAmount);//减免金额
                orderDerateVo.setRemarks("专辑折扣");//备注
                //添加至订单 减免 明细集合
                orderDerateVoList.add(orderDerateVo);
            }

        } else if (SystemConstant.ORDER_ITEM_TYPE_TRACK.equals(tradeVo.getItemType())) {
            //购买声音

            //  判断前端传递的购买集数 小于0抛出异常
            if (tradeVo.getTrackCount() < 0) {
                throw new GuiguException(ResultCodeEnum.ARGUMENT_VALID_ERROR);
            }
            //根据声音id、购买集数远程调用声音服务 获取用户下单的声音id列表
            Result<List<TrackInfo>> trackInfoListResult = trackInfoFeignClient.findPaidTrackInfoList(tradeVo.getItemId(), tradeVo.getTrackCount());
            Asserts.notNull(trackInfoListResult, "用户购买的声音id集合不存在");
            List<TrackInfo> trackInfoList = trackInfoListResult.getData();
            Asserts.notNull(trackInfoList, "用户购买的声音id集合不存在");
            //声音不支持折扣 获取声音信息 使用单价 计算价格
            Result<AlbumInfo> albumInfoResult = albumInfoFeignClient.getAlbumInfo(trackInfoList.get(0).getAlbumId());
            Asserts.notNull(albumInfoResult, "专辑不存在");
            AlbumInfo albumInfo = albumInfoResult.getData();
            Asserts.notNull(albumInfo, "专辑不存在");
            //汇总金额  //赋值属性 //声音不支持折扣
            //订单原始金额
            originalAmount = tradeVo.getTrackCount() == 0 ? albumInfo.getPrice() : albumInfo.getPrice().multiply(new BigDecimal(tradeVo.getTrackCount()));
            //订单总金额
            orderAmount = originalAmount;
            //赋值订单明细 使用.stream().map 依次遍历 通过远程调用查询的 用户下单的声音id列表
            orderDetailVoList = trackInfoList.stream().map(trackInfo -> {
                OrderDetailVo orderDetailVo = new OrderDetailVo();
                orderDetailVo.setItemId(trackInfo.getId());
                orderDetailVo.setItemName(trackInfo.getTrackTitle());
                orderDetailVo.setItemUrl(trackInfo.getCoverUrl());
                orderDetailVo.setItemPrice(albumInfo.getPrice());
                return orderDetailVo;
            }).collect(Collectors.toList());


        } else {
            //购买vip
            //获取购买的vip类型id
            Long vipId = tradeVo.getItemId();
            //远程调用用户模块的vip类型表 根据vip类型id 查询用户购买的vip套餐信息
            Result<VipServiceConfig> vipServiceConfigResult = vipServiceConfigFeignClient.getVipServiceConfig(vipId);
            Asserts.notNull(vipServiceConfigResult, "vip服务配置信息不存在");
            VipServiceConfig vipServiceData = vipServiceConfigResult.getData();
            Asserts.notNull(vipServiceData, "vip服务配置信息不存在");
            //汇总金额
            originalAmount = vipServiceData.getPrice();//订单原始金额
            derateAmount = originalAmount.subtract(vipServiceData.getDiscountPrice());//减免总金额
            orderAmount = vipServiceData.getDiscountPrice();//订单总金额

            //订单明细列表泛型
            OrderDetailVo orderDetailVo = new OrderDetailVo();
            orderDetailVo.setItemId(vipId); //付费项目id
            orderDetailVo.setItemName(vipServiceData.getName()); //付费项目名称
            orderDetailVo.setItemUrl(vipServiceData.getImageUrl()); //付费项目图片url
            orderDetailVo.setItemPrice(orderAmount);//付费项目价格
            //添加至订单 明细集合
            orderDetailVoList.add(orderDetailVo);

            //赋值减免明细，判断是否有减免
            if (derateAmount.compareTo(new BigDecimal("0")) == 1) {
                //订单减免明细列表泛型
                OrderDerateVo orderDerateVo = new OrderDerateVo();
                orderDerateVo.setDerateType(SystemConstant.ORDER_DERATE_VIP_SERVICE_DISCOUNT); //1406：订单减免类型 1405-专辑折扣 1406-VIP服务折
                orderDerateVo.setDerateAmount(derateAmount);//减免金额
                orderDerateVo.setRemarks("VIP折扣");//备注
                //添加至订单 减免 明细集合
                orderDerateVoList.add(orderDerateVo);
            }
        }

        //赋值vo
        //  交易号
        String tradeNo = UUID.randomUUID().toString().replaceAll("-", "");
        // 防重：生成一个唯一标识，保存到redis中一份
        String tradeKeyNO = "tradeNo" + userId + "tradeNo" + tradeNo;
        //存储redis setnx  防止用户无刷新 重复回退 提交订单
        this.redisTemplate.opsForValue().setIfAbsent(tradeKeyNO, tradeNo, 15, TimeUnit.MINUTES);
        //构造结果
        orderInfoVo.setTradeNo(tradeNo);//交易号
        orderInfoVo.setPayWay("");//支付方式
        orderInfoVo.setItemType(tradeVo.getItemType());//付款项目类型
        orderInfoVo.setOriginalAmount(originalAmount);//订单原始金额
        orderInfoVo.setDerateAmount(derateAmount);//减免总金额
        orderInfoVo.setOrderAmount(orderAmount);//订单总金额
        orderInfoVo.setOrderDetailVoList(orderDetailVoList);//订单明细列表
        orderInfoVo.setOrderDerateVoList(orderDerateVoList);//订单减免明细列表
        orderInfoVo.setTimestamp(SignHelper.getTimestamp());//时间戳
        //  生成签名
        //  签名： 1. 防止用户恶意篡改数据  2. 保证接口的安全性
        //  将这个orderInfoVo 对象转换为Map 集合
        Map map = JSON.parseObject(JSON.toJSONString(orderInfoVo), Map.class);
        // 将返回的数据使用 | 拼接！ 并且添加一个固定的key; 在使用md5 对当前字符串加密;
        String sign = SignHelper.getSign(map);
        orderInfoVo.setSign(sign);
        //返回结果集
        return orderInfoVo;
    }

    /**
     * 提交订单
     *
     * @param userId
     * @param orderInfoVo
     * @return
     */
    @GlobalTransactional
    @Override
    public String submitOrder(Long userId, OrderInfoVo orderInfoVo) {
        //  1.  校验签名 :
        Map map = JSON.parseObject(JSON.toJSONString(orderInfoVo), Map.class);
        map.put("payWay", "");
        SignHelper.checkSign(map);
        //  2.  校验tradeNo
        //  2.1 先获取到页面流水号;
        String tradeNo = orderInfoVo.getTradeNo();
        //  2.2 创建redis 流水号key;
        String tradeNoKey = "tradeNo" + userId + "tradeNo" + tradeNo;
        //  创建RedisScript 对象
        DefaultRedisScript<Long> redisScript = new DefaultRedisScript<>();
        //  定义lua 脚本;
        String script = "if redis.call(\"get\",KEYS[1]) == ARGV[1]\n" +
                "then\n" +
                "    return redis.call(\"del\",KEYS[1])\n" +
                "else\n" +
                "    return 0\n" +
                "end";
        redisScript.setScriptText(script);
        redisScript.setResultType(Long.class);
        //  判断是否删除成功.
        Long count = (Long) this.redisTemplate.execute(redisScript, Arrays.asList(tradeNoKey), tradeNo);
        if (count == 0) {
            throw new GuiguException(ResultCodeEnum.REPEAT_BUY_ERROR);
        }
        //  声明一个订单编号;
        String orderNo = UUID.randomUUID().toString().replaceAll("-", "");
        //  3.  判断支付方式
        if (SystemConstant.ORDER_PAY_WAY_WEIXIN.equals(orderInfoVo.getPayWay())) {
            //微信支付; 保存订单信息，并发送一个消息，来实现取消订单功能
            //  1. 保存订单信息; order_info order_detail order_derate
            this.orderSaveInfo(orderInfoVo, orderNo, userId);
            rabbitService.sendDealyMessage(MqConst.EXCHANGE_CANCEL_ORDER, MqConst.ROUTING_CANCEL_ORDER, orderNo, MqConst.CANCEL_ORDER_DELAY_TIME);
        } else { //  余额支付;

            //  1. 保存订单信息; order_info order_detail order_derate
            this.orderSaveInfo(orderInfoVo, orderNo, userId);

            //  2. 锁定账户可用金额 判断是否有可用余额; account 创建扣减金额对象AccountDeductVo
            AccountDeductVo accountDeductVo = new AccountDeductVo();
            accountDeductVo.setOrderNo(orderNo);
            accountDeductVo.setUserId(userId);
            accountDeductVo.setAmount(orderInfoVo.getOrderAmount());
            accountDeductVo.setContent(orderInfoVo.getOrderDetailVoList().get(0).getItemName());
            //  远程调用userAccountFeignClient 检查与锁定账户金额
            Result result = userAccountFeignClient.checkAndDeduct(accountDeductVo);

            if (200 != (result.getCode())) {
                //  检查扣减失败，则抛出异常！
                throw new GuiguException(result.getCode(), result.getMessage());
            }
            //扣减成功，根据订单号修改订单状态 为已支付
            OrderInfo orderInfo = new OrderInfo();
            orderInfo.setOrderStatus(SystemConstant.ORDER_STATUS_PAID);
            LambdaQueryWrapper<OrderInfo> wrapper = new LambdaQueryWrapper<OrderInfo>().eq(OrderInfo::getOrderNo, orderNo);
            this.update(orderInfo, wrapper);

            //  3. 保存用户购买交易记录; user_paid_album user_paid_track user_vip_service
            UserPaidRecordVo userPaidRecordVo = new UserPaidRecordVo();
            //  3.1 给属性赋值
            userPaidRecordVo.setOrderNo(orderNo);
            userPaidRecordVo.setUserId(userId);
            userPaidRecordVo.setItemType(orderInfoVo.getItemType());
            //  购买项目的Id 专辑Id，声音Id, 服务配置Id: 在哪? order_detail.item_id
            List<Long> itemIdList = orderInfoVo.getOrderDetailVoList().stream().map(OrderDetailVo::getItemId).collect(Collectors.toList());
            userPaidRecordVo.setItemIdList(itemIdList);
            //远程用户模块 调用保存
            Result userResult = userInfoFeignClient.savePaidRecord(userPaidRecordVo);
            //  判断远程用户模块返回的数据集 code码
            if (200 != userResult.getCode()) {
                throw new GuiguException(ResultCodeEnum.DATA_ERROR);
            }
        }
        //  返回订单编号
        return orderNo;
    }

    /**
     * RabbitMq更改订单状态 15分支未支付 发送mq更改订单状态自动 取消订单 可以在创建支付时 PrepayRequest() 设置 request.setTimeExpire(); //设置过期时间 等于取消订单的时间
     *
     * @param orderNo
     */
    @Override
    public void orderCancel(String orderNo) {
        /**
         * case1 只关orderInfo
         * case2 即关orderInfo 又关paymentInfo 说明用户一定点击了微信支付，点击了微信支付才有paymentInfo做保存
         * case3 即关orderInfo 又关paymentInfo和wxPay 远程微信交易记录 远程微信返回的信息  扫码才有的交易记录
         */
        OrderInfo orderInfo = this.getOrderInfo(orderNo);
        //判断订单 根据订单编号查询有订单信息 且 订单状态为 未支付的才 取消订单
        if (null != orderInfo && orderInfo.getOrderStatus().equals(SystemConstant.ORDER_STATUS_UNPAID)) {
/*        远程调用，根据订单编号查询是否有paymentInfo交易记录
          PaymentInfo paymentInfo = paymentInfoFeignClient.getPaymentInfo(orderNo);
            if (null != paymentInfo && paymentInfo.getOrderStatus().equals(SystemConstant.ORDER_STATUS_UNPAID)){
               查询是否有与远程微信的交易记录 扫码才有的交易记录 queryPayStatus()
               if(true){ //有微信交易记录
                  boolean result=closeWxPay();
                  if(result){
                    //关闭成功，不能支付
                    即关orderInfo 又关paymentInfo
                   }else{
                    //关闭失败 在过期的一瞬间 用户支付了
                   }
               }else{
                即关orderInfo 又关paymentInfo }
            }
         else{
            无paymentInfo，用户未点击微信支付，只关orderInfo}
*/

            //修改订单状态属性 用于使用MyBais修改订单信息表属性
            orderInfo.setOrderStatus(SystemConstant.ORDER_STATUS_CANCEL); // ORDER_STATUS_CANCEL="0903";  // 已取消
            //根据LambdaQueryWrapper 订单号条件更新数据库
            this.updateById(orderInfo);
        }

/**
 //创建订单信息实体类 修改订单状态属性 用于使用MyBais修改订单信息表属性
 OrderInfo orderInfo = new OrderInfo();
 orderInfo.setOrderStatus(SystemConstant.ORDER_STATUS_CANCEL); // ORDER_STATUS_CANCEL="0903";  // 已取消

 //根据LambdaQueryWrapper 订单号条件更新数据库
 this.update(orderInfo,new LambdaQueryWrapper<OrderInfo>().eq(OrderInfo::getOrderNo,orderNo));
 */
    }

    /**
     * 根据订单号获取订单信息
     *
     * @param tradeNo
     * @return
     */
    @Override
    public OrderInfo getOrderInfo(String tradeNo) {
        //根据订单号获取订单信息
        OrderInfo orderInfo = orderInfoMapper.selectOne(new LambdaQueryWrapper<OrderInfo>().eq(OrderInfo::getOrderNo, tradeNo));
        //赋值订单信息的支付类型 名称 余额支付 或 在线支付
        orderInfo.setPayWayName(SystemConstant.ORDER_PAY_ACCOUNT.equals(orderInfo.getPayWay()) ? "余额支付" : "在线支付");
        //获取订单明细 用于459
        List<OrderDetail> orderDetailList = this.orderDetailMapper.selectList(new LambdaQueryWrapper<OrderDetail>().eq(OrderDetail::getOrderId, orderInfo.getId()));
        if (null != orderInfo) {
            orderInfo.setOrderDetailList(orderDetailList);
        }

        return orderInfo;
    }

    /**
     * 订单列表
     *
     * @param orderInfoPage
     * @param userId
     * @param orderStatus
     * @return
     */
    @Override
    public IPage<OrderInfo> findUserPage(Page<OrderInfo> orderInfoPage, Long userId, String orderStatus) {

        IPage<OrderInfo> userPage = orderInfoMapper.selectUserPage(orderInfoPage, userId, orderStatus);

        //为查询IPage<OrderInfo>结果集 中的每条数据 赋值 支付方式名：余额支付 或 在线支付 当前订单状态：已支付、未支付 或 已取消
        userPage.getRecords().stream().forEach(orderInfo -> {
            orderInfo.setPayWayName(SystemConstant.ORDER_PAY_ACCOUNT.equals(orderInfo.getPayWay()) ? "余额支付" : "在线支付");
            orderInfo.setOrderStatusName(SystemConstant.ORDER_STATUS_PAID.equals(orderInfo.getOrderStatus()) ? "已支付" : SystemConstant.PAYMENT_STATUS_UNPAID.equals(orderInfo.getOrderStatus()) ? "未支付" : "已取消");
        });

        return userPage;
    }

    @Transactional(rollbackFor = Exception.class)
    private void orderSaveInfo(OrderInfoVo orderInfoVo, String orderNo, Long userId) {
        //保存订单信息表
        OrderInfo orderInfo = new OrderInfo();
        BeanUtils.copyProperties(orderInfoVo, orderInfo);
        orderInfo.setUserId(userId);
        orderInfo.setOrderNo(orderNo);
        orderInfo.setOrderTitle(orderInfoVo.getOrderDetailVoList().get(0).getItemName());
        orderInfo.setOrderStatus(SystemConstant.ORDER_STATUS_UNPAID);
        orderInfoMapper.insert(orderInfo);

        //保存订单减免表
        List<OrderDerateVo> orderDerateVoList = orderInfoVo.getOrderDerateVoList();
        if (!CollectionUtils.isEmpty(orderDerateVoList)) {
            for (OrderDerateVo orderDerateVo : orderDerateVoList) {
                OrderDerate orderDerate = new OrderDerate();
                BeanUtils.copyProperties(orderDerateVo, orderDerate);
                orderDerate.setOrderId(orderInfo.getId());
                orderDerateMapper.insert(orderDerate);
            }
        }

        //保存订单明细表
        List<OrderDetailVo> orderDetailVoList = orderInfoVo.getOrderDetailVoList();
        if (!CollectionUtils.isEmpty(orderDetailVoList)) {
            for (OrderDetailVo orderDetailVo : orderDetailVoList) {
                OrderDetail orderDetail = new OrderDetail();
                BeanUtils.copyProperties(orderDetailVo, orderDetail);
                orderDetail.setOrderId(orderInfo.getId());
                orderDetailMapper.insert(orderDetail);
            }
        }
    }

    /**
     * 监听当前订单号不为空 更新订单状态 0902 已支付  记录用户的购买记录
     *
     * @param orderNo
     */
    @Override
    public void orderPaySuccess(String orderNo) {
        //修改订单状态 1402已支付 记录用户的购买记录
        OrderInfo orderInfo = this.getOrderInfo(orderNo);
//        //根据订单号查询的订单信息为空 直接返回 判断范围大 需要修改为 判断非空的同时 订单状态为 未支付 则执行后续保存流程
//        if (null==orderInfo) {
//            return;
//        }

        if (null != orderInfo && orderInfo.getOrderStatus().equals(SystemConstant.ORDER_STATUS_UNPAID)) {
            //根据订单号查询的订单信息不为空   更新订单状态 0902 已支付  记录用户的购买记录
            //设置订单的支付状态 为已付款
            orderInfo.setOrderStatus(SystemConstant.ORDER_STATUS_PAID); //0902";  // 已支付
            //执行更新操作
            this.updateById(orderInfo);
            //记录用户的购买记录

            //  3. 保存用户购买交易记录; user_paid_album user_paid_track user_vip_service
            UserPaidRecordVo userPaidRecordVo = new UserPaidRecordVo();
            //  3.1 给属性赋值
            userPaidRecordVo.setOrderNo(orderNo);
            userPaidRecordVo.setUserId(orderInfo.getUserId());
            userPaidRecordVo.setItemType(orderInfo.getItemType());
            //  购买项目的Id 专辑Id，声音Id, 服务配置Id: 在哪? order_detail.item_id
            List<Long> itemIdList = orderInfo.getOrderDetailList().stream().map(OrderDetail::getItemId).collect(Collectors.toList());
            userPaidRecordVo.setItemIdList(itemIdList);
            //远程用户模块 调用保存
            Result userResult = userInfoFeignClient.savePaidRecord(userPaidRecordVo);
        }
    }
}
